package com.eastfair.venuebooking.controller;

import com.baomidou.mybatisplus.core.metadata.IPage;
import com.eastfair.annotation.annotation.base.BaseControllerInfo;
import com.eastfair.annotation.annotation.log.SysLog;
import com.eastfair.annotation.annotation.security.PreAuth;
import com.eastfair.boot.controller.SuperController;
import com.eastfair.boot.request.PageParams;
import com.eastfair.core.base.R;
import com.eastfair.core.context.ContextUtil;
import com.eastfair.echo.core.EchoService;
import com.eastfair.venuebooking.demand.QuotationGroup;
import com.eastfair.venuebooking.dto.*;
import com.eastfair.venuebooking.entity.Quotation;
import com.eastfair.venuebooking.service.QuotationDetailService;
import com.eastfair.venuebooking.service.QuotationService;
import com.eastfair.venuebooking.vo.PriceListSpaceVO;
import com.eastfair.venuebooking.vo.QuotationVO;
import io.swagger.annotations.Api;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.*;

import javax.annotation.Resource;
import javax.validation.constraints.NotEmpty;
import javax.validation.constraints.NotNull;
import java.util.ArrayList;
import java.util.List;
import java.util.Map;
import java.util.stream.Collectors;


/**
 * <p>
 * 前端控制器
 * 报价书
 * </p>
 *
 * @author linan
 * @date 2022-06-08
 */
@Slf4j
@Validated
@RestController
@RequestMapping("/quotation")
@Api(value = "Quotation", tags = "报价书")
@PreAuth(replace = "venuebooking:quotation:")
public class QuotationController extends SuperController<QuotationService, Long, Quotation, QuotationPageQuery, QuotationSaveDTO, QuotationUpdateDTO> {

    @Autowired
    private EchoService echoService;

    @Resource
    private QuotationService quotationService;

    @Resource
    private QuotationDetailService quotationDetailService;

    @Override
    public void handlerResult(IPage<Quotation> page) {
        // 想让返回值实现自动回显，请将此行代码打开
        // echoService.action(page);
    }

    /**
     * Excel导入后的操作
     *
     * @param list
     */
    @Override
    public R<Boolean> handlerImport(List<Map<String, String>> list) {
        List<Quotation> quotationList = list.stream().map((map)
                -> Quotation.builder().build()).collect(Collectors.toList());
        return R.success(baseService.saveBatch(quotationList));
    }


    /**
     * 处理参数
     *
     * @param params 分页参数
     */
    @Override
    public void handlerQueryParams(PageParams<QuotationPageQuery> params) {
        QuotationPageQuery pageQuery = params.getModel();
        //分页处理
        if (ContextUtil.getProjectId() != null) {
            pageQuery.setProjectId(ContextUtil.getProjectId());
        }
    }

    /**
     * 分页查询报价记录.
     *
     * @return the r
     */
    @PostMapping("/page/quotation")
    @BaseControllerInfo(voGroup = {QuotationGroup.QueryQuotation.class})
    public R<IPage<QuotationVO>> queryQuotation(@RequestBody PageParams<QuotationQuery> pageParams) {
        log.info("pageQuotation - 分页查询报价记录, pageParams={}", pageParams);
        return R.successDef(quotationService.listQuotationVOs(pageParams));
    }


    /**
     * 查询展会下可以生成合同的报价书.
     *
     * @param exhibitionId the exhibition id
     * @return the r
     */
    @GetMapping("/for/contractManage/{exhibitionId}")
    public R<List<QuotationVO>> queryForContractManage(@PathVariable("exhibitionId") Long exhibitionId) {
        log.info("queryForContractManage - 查询展会下可以生成合同的报价书, exhibitionId={}", exhibitionId);
        return R.successDef(quotationService.listForContractManage(exhibitionId));
    }

    /**
     * 查询报价书的所有展厅.
     *
     * @return the r
     */
    @PostMapping("/queryAllSpace")
    public R<List<PriceListSpaceVO>> queryAllSpace(@RequestBody QuotationQuery query) {
        log.info("queryAllSpace - 查询报价书的所有展厅, query={}", query);
        return R.successDef(quotationService.queryAllSpace(query));
    }

    /**
     * id查询报价书.
     *
     * @param id the id
     * @return the by id
     */
    @GetMapping("/get/{id}")
    public R<QuotationVO> getById(@PathVariable("id") Long id) {
        log.info("getById - id查询报价书, id={}", id);
        return R.successDef(quotationService.getQuotationVOById(id));
    }

    /**
     * 报价书id查询场地价目.
     *
     * @param id the id
     * @return the r
     */
    @GetMapping("/priceListSpace/{id}")
    @BaseControllerInfo(voGroup = {QuotationGroup.QueryPriceListSpace.class})
    public R<List<PriceListSpaceVO>> queryPriceListSpace(@PathVariable Long id) {
        log.info("queryPriceListSpace - 报价书id查询场地价目, id={}", id);
        return R.successDef(quotationService.listPriceListSpacesByQuotationId(id));
    }

    /**
     * 新增报价书.
     *
     * @param quotationDTO the quotation dto
     * @return the r
     */
    @SysLog("添加报价书")
    @PostMapping("/save")
    public R<Boolean> saveQuotation(@RequestBody @Validated({QuotationDTO.Save.class}) QuotationDTO quotationDTO) {
        log.info("saveQuotation - 新增报价书, quotationDTO={}", quotationDTO);
        return R.successDef(quotationService.saveQuotation(quotationDTO));
    }

    /**
     * 新增展会报价书.
     *
     * @param quotationDTO the quotation dto
     * @return the r
     */
    @SysLog("添加展会报价书")
    @PostMapping("/exhibition/save")
    public R<Boolean> saveExhibitionQuotation(@RequestBody
                                              @Validated({QuotationDTO.Update.class, QuotationDTO.SaveExhibition.class})
                                              QuotationDTO quotationDTO) {
        log.info("saveExhibitionQuotation - 新增展会报价书, quotationDTO={}", quotationDTO);
        return R.successDef(quotationService.saveExhibitionQuotation(quotationDTO));
    }

    /**
     * 更新报价书.
     *
     * @param quotationDTO the quotation dto
     * @return the r
     */
    @SysLog("修改报价书")
    @PostMapping("/update")
    public R<Boolean> updateQuotation(@RequestBody
                                      @Validated({QuotationDTO.Save.class, QuotationDTO.Update.class})
                                      QuotationDTO quotationDTO) {
        log.info("updateQuotation - 更新报价书, quotationDTO={}", quotationDTO);
        return R.successDef(quotationService.updateQuotation(quotationDTO));
    }

    /**
     * 删除报价书.
     *
     * @param id id
     * @return the r
     */
    @SysLog("删除报价书")
    @GetMapping("/removeQuotation")
    public R<Boolean> deleteQuotation(@RequestParam("id") @Validated @NotNull(message = "报价书ID必填") Long id) {
        log.info("deleteQuotation - 删除报价书, id={}", id);
        List<Long> list = new ArrayList<>();
        list.add(id);
        return R.successDef(quotationService.removeQuotationByIds(list));
    }

    /**
     * 批量删除报价书.
     *
     * @param ids the ids
     * @return the r
     */
    @SysLog("批量删除报价书")
    @PostMapping("/removeQuotationList")
    public R<Boolean> deleteQuotation(@RequestBody @NotEmpty(message = "报价书ID列表不可为空") List<Long> ids) {
        log.info("deleteQuotation - 删除报价书, ids={}", ids);
        return R.successDef(quotationService.removeQuotationByIds(ids));
    }

    /**
     * 批量删除报价书详情.
     *
     * @param quotationDTO the quotation dto
     * @return the r
     */
    @Deprecated
    @SysLog("批量删除报价书详情")
    @PostMapping("/removeQuotationDetail")
    public R<Boolean> deleteQuotationDetail(@RequestBody QuotationDTO quotationDTO) {
        log.info("deleteQuotationDetail - 删除报价书详情, quotationDTO={}", quotationDTO);
        return R.successDef(quotationService.removeQuotationDetail(quotationDTO));
    }

    /**
     * 验证计价时长.
     *
     * @param quotationDTO the quotation dto
     * @return the r
     */
    @PostMapping("/valid/priceDuration")
    public R<Map<String, Object>> validPriceDuration(@RequestBody
                                                     @Validated({QuotationDTO.Save.class})
                                                     QuotationDTO quotationDTO) {
        log.info("validPriceDuration - 验证计价时长, quotationDTO={}", quotationDTO);
        return R.successDef(quotationService.validQuotationPriceDuration(quotationDTO));
    }
}
